<template>
	<div class="default-main">

		<cus-form id="log-form" collapsable icon="fa fa-search" label="搜索">
			<template #title-after>
				<el-button :loading="loading" icon="el-icon-Search" size="small" type="primary" @click.stop="handleSearch">
					搜索
				</el-button>
				<el-button :loading="loading" icon="el-icon-Refresh" size="small" type="primary" @click.stop="resetSearch">
					重置
				</el-button>
			</template>
			<template #form>
				<el-form ref="searchForm" :model="params" label-width="auto">
					<el-row :gutter="20" justify="space-between">
						<el-col :span="8">
							<el-form-item label="操作人">
								<el-input v-model="params.operator_like" clearable placeholder="模糊查询"
								          @keyup.enter="handleSearch"></el-input>
							</el-form-item>
						</el-col>
						<el-col :span="8">
							<el-form-item label="方法名称">
								<el-input v-model="params.methodName_like" clearable placeholder="模糊查询"
								          @keyup.enter="handleSearch"></el-input>
							</el-form-item>
						</el-col>
						<el-col :span="8">
							<el-form-item label="方法描述">
								<el-input v-model="params.methodDescription_like" clearable placeholder="模糊查询"
								          @keyup.enter="handleSearch"></el-input>
							</el-form-item>
						</el-col>
					</el-row>
					<el-row :gutter="20" justify="space-between">
						<el-col :span="8">
							<el-form-item label="请求地址">
								<el-input v-model="params.requestUrl_like" clearable placeholder="模糊查询"
								          @keyup.enter="handleSearch"></el-input>
							</el-form-item>
						</el-col>
						<el-col :span="8">
							<el-form-item label="IP">
								<el-input v-model="params.ip_like" clearable placeholder="模糊查询"
								          @keyup.enter="handleSearch"></el-input>
							</el-form-item>
						</el-col>
						<el-col :span="8">
							<el-form-item label="状态码">
								<el-input-number v-model="params.statusCode_like" class="w100" clearable controls-position="right" placeholder="模糊查询"
								                 step-strictly @keyup.enter="handleSearch"/>
							</el-form-item>
						</el-col>
					</el-row>
					<el-row :gutter="20" justify="space-between">
						<el-col :span="8">
							<el-form-item label="执行时间不小于(ms)">
								<el-input-number v-model="params.minExecutionTime" :min="1" class="w100" clearable controls-position="right"
								                 step-strictly @keyup.enter="handleSearch"/>
							</el-form-item>
						</el-col>
						<el-col :span="8">
							<el-form-item :label="$t('system.log.createTimeFrom')">
								<el-date-picker v-model="params.createTimeFrom" :default-time="<any>new Date(2000,1,1,0,0,0, 0)" class="w100" clearable
								                placeholder="可选" type="datetime" @change="handleSearch"/>
							</el-form-item>
						</el-col>
						<el-col :span="8">
							<el-form-item :label="$t('system.log.createTimeTo')">
								<el-date-picker v-model="params.createTimeTo" :default-time="<any>new Date(2000,1,1,23,59,59, 999)" class="w100" clearable placeholder="可选"
								                type="datetime" @change="createTimeToChanged"/>
							</el-form-item>
						</el-col>
					</el-row>
					<el-row :gutter="20" justify="space-between">
						<el-col :span="8">
							<el-form-item label="执行结果">
								<el-input v-model="params.message_like" clearable placeholder="模糊查询" @keyup.enter="handleSearch"></el-input>
							</el-form-item>
						</el-col>
						<el-col :span="8">
							<el-form-item label="仅错误">
								<el-switch v-model="params.errorOnly" @change="handleSearch"></el-switch>
							</el-form-item>
						</el-col>
						<el-col :span="8">
							<el-form-item label="过滤系统日志查询">
								<el-switch v-model="params.recordsOfSystemLogQueryNotIncluded" @change="handleSearch"></el-switch>
							</el-form-item>
						</el-col>
					</el-row>
				</el-form>
			</template>
		</cus-form>

		<cus-table-title id="log-table-title" icon="local-cus-log" label="系统日志"/>
		<el-table ref="tableRef" v-loading="loading" :data="systemLogTableData" :header-cell-class-name="handleHeaderCellClass" :max-height="tableMaxHeight"
		          border class="cus-table" fit highlight-current-row show-overflow-tooltip @sort-change="elTableSortChange($event, params.orderby, handleSearch)">
			<el-table-column align="center" fixed="left" label="序号" width="100">
				<template v-slot="scope">
					{{ initTableIndex(pageRef, scope.$index) }}
				</template>
			</el-table-column>
			<el-table-column align="center" label="操作人" prop="operator" width="150"></el-table-column>
			<el-table-column align="center" label="方法名称" prop="methodName" width="200"></el-table-column>
			<el-table-column align="center" label="方法描述" prop="methodDescription" width="200"></el-table-column>
			<el-table-column align="center" label="请求地址" min-width="250" prop="requestUrl"></el-table-column>
			<el-table-column align="center" label="IP地址" prop="ip" width="150"></el-table-column>
			<el-table-column align="center" label="执行耗时(毫秒)" prop="executionTime" sortable="custom" width="150"></el-table-column>
			<el-table-column align="center" label="状态码" prop="statusCode" sortable="custom" width="100">
				<template v-slot="{row}">
					<el-text :type="row.statusCode === 200 ? 'success' : 'danger'">{{ row.statusCode }}</el-text>
				</template>
			</el-table-column>
			<el-table-column align="center" label="执行结果" min-width="500" prop="message">
				<template v-slot="{row}">
					<el-text :type="row.statusCode === 200 ? 'success' : 'danger'" truncated>{{ row.message }}</el-text>
				</template>
			</el-table-column>
			<el-table-column align="center" label="执行结束时间" prop="createTime" sortable="custom" width="200"></el-table-column>
		</el-table>
		<cus-pagination id="log-pagination" ref="pageRef" v-model="systemLogTableData" v-model:loading="loading" :pageSize="100" :params="params"
		                url="/system/sys-log/readOnly/pageSystemLog"/>

	</div>
</template>

<script lang="ts" name="SystemLog" setup>

import {elTableHeaderCellClassName, elTableSortChange, initTableIndex} from '@/utils/commonUtil'
import {onActivated, onMounted, reactive, ref} from 'vue'
import CusTableTitle from '@/components/cus-table-title.vue'
import CusPagination from '@/components/cus-pagination.vue'
import {calcMaxHeight} from '@/utils/layoutUtil'
import {useEventListener} from '@vueuse/core'
import {onBeforeRouteLeave} from 'vue-router'
import {debounce, type DebouncedFunc} from 'lodash-es'
import type {TableColumnCtx} from 'element-plus'
import CusForm from '@/components/cus-form.vue'

const tableRef = ref()
const tableMaxHeight = ref<number>(800)
const loading = ref(false)
const params = reactive({
	operator_like: undefined,
	methodName_like: undefined,
	methodDescription_like: undefined,
	requestUrl_like: undefined,
	ip_like: undefined,
	minExecutionTime: undefined,
	statusCode_like: undefined,
	message_like: undefined,
	createTimeFrom: undefined,
	createTimeTo: undefined,
	errorOnly: true,
	recordsOfSystemLogQueryNotIncluded: true,
	orderby: []
})
const systemLogTableData = ref([])
const pageRef = ref()

// 计算表格最大高度
const getTableMaxHeight: DebouncedFunc<() => typeof getTableMaxHeight> = debounce(() => {
	tableMaxHeight.value = calcMaxHeight('#log-form', '#log-table-title', '#log-pagination')
	return getTableMaxHeight
}, 100, {
	leading: true,
	trailing: false,
	maxWait: 100
})

const handleHeaderCellClass = (args: { rows: SysLog[], column: TableColumnCtx<SysLog>, rowIndex: number, columnIndex: number }) => {
	elTableHeaderCellClassName(args, params.orderby)
}

const handleSearch = () => {
	pageRef.value.reload()
}

const resetParams = () => {
	params.operator_like = undefined
	params.methodName_like = undefined
	params.methodDescription_like = undefined
	params.requestUrl_like = undefined
	params.ip_like = undefined
	params.minExecutionTime = undefined
	params.statusCode_like = undefined
	params.message_like = undefined
	params.createTimeFrom = undefined
	params.createTimeTo = undefined
	params.errorOnly = true
	params.recordsOfSystemLogQueryNotIncluded = true
	params.orderby = []
	// 清除多列的排序状态
	for (const column of tableRef.value?.store.states.columns.value) {
		column.order = null
	}
}

const resetSearch = () => {
	resetParams()
	handleSearch()
}

// 设置截止时间的毫秒为999
const createTimeToChanged = (val: Date) => {
	if (val) {
		val.setMilliseconds(999)
		val.setUTCMilliseconds(999)
	}
	handleSearch()
}

onMounted(() => {
	useEventListener(window, 'resize', getTableMaxHeight()!)
})

// 该页面开启缓存且首次或后续进入时执行，刷新页面不执行
onActivated(() => {
	useEventListener(window, 'resize', getTableMaxHeight()!)
})

onBeforeRouteLeave(() => {
	window.removeEventListener('resize', getTableMaxHeight)
})

</script>

<style lang="scss" scoped>
</style>
